package com.leonzhangxf.spel.reference;

import com.leonzhangxf.spel.reference.bean.Inventor;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.expression.EvaluationContext;
import org.springframework.expression.ExpressionParser;
import org.springframework.expression.spel.standard.SpelExpressionParser;
import org.springframework.expression.spel.support.SimpleEvaluationContext;

/**
 * Elvis Operator
 *
 * <p>
 * The Elvis operator is a shortening of the ternary operator syntax and is used in the Groovy language.
 * With the ternary operator syntax, you usually have to repeat a variable twice,
 * as the following example shows:
 *
 * <code>
 * String name = "Elvis Presley";
 * String displayName = (name != null ? name : "Unknown");
 * </code>
 *
 * <p>
 * Instead, you can use the Elvis operator (named for the resemblance to Elvis' hair style).
 * The following example shows how to use the Elvis operator:
 *
 * <code>
 * ExpressionParser parser = new SpelExpressionParser();
 * String name = parser.parseExpression("name?:'Unknown'").getValue(String.class);
 * System.out.println(name);  // 'Unknown'
 * </code>
 *
 * <p>
 * Note:
 * You can use the Elvis operator to apply default values in expressions.
 * The following example shows how to use the Elvis operator in a {@link Value} expression:
 * <code>
 * {@link org.springframework.beans.factory.annotation.Value}("#{systemProperties['pop3.port'] ?: 25}")
 * </code>
 * This will inject a system property pop3.port if it is defined or 25 if not.
 *
 * @author leonzhangxf
 * @date 20190427
 */
public class ElvisOperator {

    public static void main(String[] args) {
        ExpressionParser parser = new SpelExpressionParser();
        EvaluationContext context = SimpleEvaluationContext.forReadOnlyDataBinding().build();

        Inventor tesla = new Inventor("Nikola Tesla", "Serbian");
        String name = parser.parseExpression("Name?:'Elvis Presley'")
            .getValue(context, tesla, String.class);
        // Nikola Tesla
        System.out.println(name);

        tesla.setName(null);
        name = parser.parseExpression("Name?:'Elvis Presley'")
            .getValue(context, tesla, String.class);
        // Elvis Presley
        System.out.println(name);
    }
}
